package com.m1book.domain;

import java.text.SimpleDateFormat;
import java.util.Date;
import java.util.Random;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.w3c.dom.Document;

import com.m1book.domain.book.ABook;
import com.m1book.domain.book.Book;
import com.m1book.domain.trace.DonaABookTrace;
import com.m1book.domain.user.Miser;
import com.m1book.domain.util.DoubanBookUtil;
import com.m1book.repositories.book.ABookRepository;
import com.m1book.repositories.book.BookRepository;
import com.m1book.repositories.trace.RegisterABookTraceRepository;
import com.m1book.repositories.user.MiserRepository;

/**
 * {@link M1BookService}的实现类，实现了咪书网的业务功能逻辑。
 * @author Frankie
 *
 */
@Service
public class M1BookServiceImpl implements M1BookService {
	private static final Logger logger = LoggerFactory.getLogger(M1BookServiceImpl.class);
	
	@Autowired
	private ABookRepository abookRepository;
	
	@Autowired
	private MiserRepository miserRepository;
	
	@Autowired
	private BookRepository bookRepository;
	
	@Autowired
	private RegisterABookTraceRepository registerABookTraceRepository;
	
	@Override
	public String registerABook(Miser miser, ABook abook) {
		SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd");
		Date now = new Date();
		
		String abookSigning = miser.getInfo().getNickname().toUpperCase() + "-" + sdf.format(now) 
				+ "-" + Long.toString(Math.abs(new Random().nextLong())).substring(0, 3);
		abook.setAbookSigning(abookSigning);
		
		DonaABookTrace trace = new DonaABookTrace();
		trace.setTraceDate(now);
		trace.setAbookId(abook.getId());
		
		abook.getDonaTraces().add(trace);
		
		registerABookTraceRepository.save(trace);
		abook = abookRepository.save(abook);
		miserRepository.save(miser);
		logger.info("save abook: " + abook.toString() + " ok.");
		logger.info("trace register abook: " + trace.toString());
		return abookSigning;
	}

	@Override
	public boolean donaABook(Miser miser, ABook abook)
			throws AuthorizationExeption, ABookStateException {
		// TODO Auto-generated method stub
		return false;
	}

	@Override
	public boolean cancelDona(Miser miser, ABook abook)
			throws AuthorizationExeption, ABookStateException {
		// TODO Auto-generated method stub
		return false;
	}

	@Override
	public String applyM1ABook(Miser miser, ABook abook)
			throws AuthorizationExeption {
		// TODO Auto-generated method stub
		return null;
	}

	@Override
	public void anwserApplyM1ABook(Miser holder, ABook abook,
			String applySequnceCode, int anwser) throws AuthorizationExeption {
		// TODO Auto-generated method stub

	}

	@Override
	public void confirmM1ABook(Miser miser, ABook abook,
			String applySequenceCode, String message)
			throws AuthorizationExeption {
		// TODO Auto-generated method stub

	}

	@Override
	public Book searchBookByISBNFromLocal(String isbn) throws BookNotExistException {
		Book book = null;
		if (isbn.length() == 10) {
			book = bookRepository.findByIsbn10(isbn);
		} else if (isbn.length() == 13) {
			book = bookRepository.findByIsbn13(isbn);
		}
		
		if (book == null) {
			throw new BookNotExistException("not found book by isbn: " + isbn + " from local.");
		} else {
			return book;
		}
	}

	@Override
	public Book searchBookByISBNFromDouban(String isbn)	throws BookNotExistException {
		Book book = null;
		/*
		try {
			SimpleClientHttpRequestFactory factory = new SimpleClientHttpRequestFactory();
			URI uri = new URI("http://api.douban.com/book/subject/isbn/" + isbn);
			ClientHttpRequest request = factory.createRequest(uri, HttpMethod.GET);
			ClientHttpResponse response = request.execute();
			if (response.getStatusCode().compareTo(HttpStatus.OK) == 0) {
				byte[] b = new byte[512];
				StringBuffer sb = new StringBuffer();
				while (response.getBody().read(b) != -1) {
					sb.append(new String(b, "utf-8"));
					b = new byte[512];
				}
				logger.info("get book isbn: " + isbn + " success.");
				
				Document document = DoubanBookUtil.parse(sb.toString());
				book = DoubanBookUtil.buildBook(document);
			}
		} catch (URISyntaxException e) {
			logger.error(e.getMessage());
		} catch (IOException e) {
			logger.error(e.getMessage());
		}
		*/
		
		Document document = DoubanBookUtil.pareseByURI("http://api.douban.com/book/subject/isbn/" + isbn);
		book = DoubanBookUtil.buildBook(document);
		
		if (book == null) {
			throw new BookNotExistException("not found book by isbn: " + isbn + " from douban.");
		} else {
			boolean localExists = false;
			int length = isbn.length();
			if (length == 10) {
				localExists = bookRepository.findByIsbn10(isbn) != null;
			} else {
				localExists = bookRepository.findByIsbn13(isbn) != null;
			}
			
			// if found book by ISNB from DOUBAN and not exists in local, we should persistent locally.
			if (!localExists) {
				bookRepository.save(book);
			}
		}
		
		return book;
	}
	
}
